<template>
    <div>
        <el-form :model="form">
            <el-form-item>
                <div class="text-right">
                    <el-button @click="onUpdateSubmit">更新</el-button>
                    <el-button :loading="requestLoading" @click="onSyncSwagger">同步Swagger</el-button>
                </div>
            </el-form-item>
            <el-form-item required label="Swagger地址">
                <el-input v-model="form.url" />
            </el-form-item>
            <el-form-item label="预处理函数">
                <div id="editor"></div>
            </el-form-item>
            
        </el-form>
    </div>
</template>

<script>
import { defineComponent, onMounted, reactive, ref } from '@vue/composition-api';
import ace from "ace-code";
import aceJsMode from "ace-code/src/mode/javascript";
import languageTools from "ace-code/src/ext/language_tools";
import { getProjectSwaggerOne, updateProjectSwagger } from '@/api/projectSwagger'
import { useApiStore } from "@/store/api";
import { syncSwagger } from '@/api/api'

export default defineComponent({


    setup() {
        const apiStore = useApiStore();
        const requestLoading = ref(false)
        const form = reactive({
            id: null,
            url: '',
            preFunction: '',
        })

        function fetchProjectSwagger() {
            getProjectSwaggerOne({
                projectId: apiStore.projectId
            }).then(res => {
                const data = res.data
                form.url = data.url
                form.preFunction = data.preFunction
                form.id = data.id
                editor.setValue(data.preFunction)
            })

        }

        fetchProjectSwagger()

        function onUpdateSubmit() {
            const handleStr = editor.getValue();
            form.preFunction = handleStr
            updateProjectSwagger({
                projectId: apiStore.projectId,
                ...form
            })
                .then(res => {
                    form.id = res.data.id
                })
        }

        function onSyncSwagger() {
            const params = {};
            const resultHeaders = {
            };
            const forms = [];

            const requestParam = {
                url: form.url,
                method: 'GET',
                params: {

                },
            };
            let _timestamp = Date.now();
            function exec(options, callback) {
                if (!options.method) {
                    options.method = 'GET'
                }
                window.postMessage({
                    __SIGNAL__: "req",
                    timestamp: _timestamp,
                    data: { __SIGNAL__: "req", timestamp: _timestamp, ...options },
                });
                window.onmessage = function (e) {
                    const { timestamp, data, __SIGNAL__ } = e.data;
                    if (__SIGNAL__ === "res" && timestamp === _timestamp) {
                        callback(timestamp, data);
                    }
                };
            }
            window.fetchExec = function (url, o) {
                console.log(url)
                return new Promise((resolve) => {
                    exec({ url, ...o }, (timestamp, data) => {
                        resolve(data.data);
                    });
                });
            };
            requestLoading.value = true;

            let doc = ''
            console.log(form.preFunction)
            if (form.preFunction) {
                const AsyncFunction = async function () { }.constructor;
                const handleFun = new AsyncFunction("doc", form.preFunction);
                const startDate = new Date();
                exec(requestParam, (timestamp, data) => {
                    doc = data.data
                    console.log('pre')
                    handleFun(doc)
                        .then(() => {
                            return syncSwagger({
                                projectId: apiStore.projectId,
                                doc
                            })
                        }).finally(() => {
                            requestLoading.value = false;
                        })
                });
            } else {
                const startDate = new Date();
                exec(requestParam, (timestamp, data) => {
                    doc = data.data

                    syncSwagger({
                        projectId: apiStore.projectId,
                        doc
                    }).finally(() => {
                        requestLoading.value = false;
                    })
                });
            }
        }

        let editor = null;
        onMounted(() => {
            editor = ace.edit("editor");
            editor.setValue(form.preFunction);
            editor.session.setMode(new aceJsMode.Mode());
            var tangideCompleter = {
                getCompletions: function (editor, session, pos, prefix, callback) {
                    if (prefix.length === 0) {
                        return callback(null, []);
                    } else {
                        return callback(null, [
                            {
                                meta: "function",
                                caption: "addShape",
                                value: "addShape",
                                score: 1,
                            },
                        ]);
                    }
                },
            };
            editor.setOptions({
                enableBasicAutocompletion: true,
                enableSnippets: true,
                enableLiveAutocompletion: true,
            });
            languageTools.addCompleter(tangideCompleter);
        });

        return {
            form,
            onUpdateSubmit,
            onSyncSwagger,
            requestLoading
        }
    }

})

</script>

<style scoped>
#editor {
    width: 100%;
    height: 400px;
}
</style>